#ifndef COMPONENTEALMACENAMIENTO_H_
#define COMPONENTEALMACENAMIENTO_H_

#include "../Dato.h"
#include "../../enums/TipoSerializacion.h"
#include "../../enums/TipoMemoria.h"
#include "../../enums/TipoPKException.h"
#include "../../enums/TipoIdException.h"
#include "../../exceptions/PKException.h"
#include "../../exceptions/IdException.h"
#include "../PrimaryKey.h"

using namespace std;

class ComponenteAlmacenamiento{
		protected:
			int id;
			TipoMemoria tipoMemoria;
			unsigned int tamanio;
	
		public:
				
		static const int idSinAsignar = -1;	
		
		/**
		 * @author emilio
		 * @return int id
		 * @version
		 */
		int getId();
		
		/**
		 * @author emilio
		 * @param void** accesoDato
		 * @return void
		 * @version
		 */
		virtual void getAccesoDato(void** accesoDato)=0;
		
		/**
		 * @author emilio
		 * @return int id
		 * @version
		 */
		unsigned int getTamanio();
		
		/**
		 * @author emilio
		 * @return TipoMemoria tipo
		 * @version
		 */
		TipoMemoria getTipoMemoria();
		
		/**
		 * <b>Escribe el registro.</b> Si no se puede escribir porque hay alg&uacute;n 
		 * problema en el almacenamiento, se arroja una excepci&oacute;n que herede de
		 * StorageException. 
		 * 
		 * @author emilio
		 * @throws StorageException
		 * @throws NullPointerException
		 * @throws IdException
		 * @param void* accesoDato
		 * @param Dato* dato (opcional)
		 * @version
		 */
		virtual void escribir(void *accesoDato,TipoSerializacion modo)=0;
		
		/**
		 * <b>Actualiza el registro.</b> Si no se puede escribir porque hay 
		 * alg&uacute;n problema en el almacenamiento, se arroja una excepci&oacute;n 
		 * que herede de StorageException. Si el id del nuevo dato no coincide con el 
		 * anterior se arroja una excepci&oacute;n de la clase IdException.
		 * 
		 * @author emilio
		 * @throws StorageException
		 * @throws NullPointerException
		 * @throws IdException
		 * @param TipoSerializacion modo
		 * @param void* accesoDato
		 * @param Dato* dato (opcional)
		 * @version
		 */
		virtual void escribir(void *accesoDato, Dato *dato, TipoSerializacion modo)=0;		 
				 
		/**
		 * <b>Escribe el registro.</b> Si no se puede escribir porque hay alg&uacute;n 
		 * problema en el almacenamiento, se arroja una excepci&oacute;n que herede de
		 * StorageException. 
		 * 
		 * @author emilio
		 * @throws StorageException
		 * @throws NullPointerException
		 * @throws IdException
		 * @param Dato* dato (opcional)
		 * @version
		 */
		virtual void escribir(TipoSerializacion modo)=0;

		/**
		 * <b>Lee el registro.</b> Si no se puede leer porque hay alg&uacute;n
		 * problema en el almacenamiento, se arroja una excepci&oacute;n que herede de
		 * StorageException.
		 * 
		 * @author emilio
		 * @throws StorageException
		 * @throws NullPointerException
		 * @param TipoSerializacion modo
		 * @param  Dato *datoLeido (debe venir vacio)
		 * @version
		 */
		virtual void leer(Dato *datoLeido, TipoSerializacion modo)=0;
		
		/**
		 * <b>Lee el registro.</b> Si no se puede leer porque hay alg&uacute;n
		 * problema en el almacenamiento, se arroja una excepci&oacute;n que herede de
		 * StorageException.
		 * 
		 * @author emilio
		 * @throws StorageException
		 * @throws NullPointerException
		 * @param TipoSerializacion modo
		 * @param  char** datoLeido(debe apuntar a null antes de la llamada)
		 * @version
		 */
		virtual void leer(char **datoLeido, TipoSerializacion modo)=0;
		
		/**
		 * <b>Borra el registro.</b> Si no se puede borrar porque hay alg&uacute;n 
		 * problema en el almacenamiento, se arroja una excepci&oacute;n que herede de
		 * StorageException. 
		 * 
		 * @author emilio
		 * @throws StorageException
		 * @throws NullPointerException
		 * @version
		 */
		virtual void borrar()=0;
		
};

#endif /*COMPONENTEALMACENAMIENTO_H_*/
